unit TambahPemilih;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ZAbstractTable, ZDataset, DB, ZAbstractRODataset,
  ZAbstractDataset, ZConnection, Grids, JvExGrids, JvStringGrid, Setting,
  cxStyles, cxCustomData, cxGraphics, cxFilter, cxData, cxDataStorage,
  cxEdit, cxDBData, cxGridCustomTableView, cxGridTableView, cxGridLevel,
  cxClasses, cxControls, cxGridCustomView, cxGridDBTableView, cxGrid,
  cxCalendar, cxDropDownEdit, ExtCtrls, JvThread, JvThreadDialog,
  JvComponentBase,Unit_External,ComObj,ActiveX;

type
  TForm_TambahPemilih = class(TForm)
    ZConnection1: TZConnection;
    ZQuery1: TZQuery;
    ZTable1: TZTable;
    GroupBox1: TGroupBox;
    cxGrid1DBTableView1: TcxGridDBTableView;
    cxGrid1Level1: TcxGridLevel;
    cxGrid1: TcxGrid;
    cxGrid1TableView1: TcxGridTableView;
    cxGrid1TableView1Column1: TcxGridColumn;
    cxGrid1TableView1Column2: TcxGridColumn;
    cxGrid1TableView1Column3: TcxGridColumn;
    cxGrid1TableView1Column4: TcxGridColumn;
    cxGrid1TableView1Column5: TcxGridColumn;
    cxGrid1TableView1Column7: TcxGridColumn;
    cxGrid1TableView1Column8: TcxGridColumn;
    cxGrid1TableView1Column9: TcxGridColumn;
    cxGrid1TableView1Column10: TcxGridColumn;
    cxGrid1TableView1Column12: TcxGridColumn;
    cxGrid1TableView1Column13: TcxGridColumn;
    cxGrid1TableView1Column14: TcxGridColumn;
    cxGrid1TableView1Column6: TcxGridColumn;
    ZQuery2: TZQuery;
    Timer1: TTimer;
    cxGrid1TableView1Column11: TcxGridColumn;
    cxGrid1TableView1Column16: TcxGridColumn;
    cxGrid1TableView1Column17: TcxGridColumn;
    cxGrid1TableView1Column18: TcxGridColumn;
    cxGrid1TableView1Column19: TcxGridColumn;
    qryCek: TZQuery;
    OpenDialog1: TOpenDialog;
    JvThread2: TJvThread;
    JvThreadSimpleDialog2: TJvThreadSimpleDialog;
    Panel1: TPanel;
    Label2: TLabel;
    fileloc: TEdit;
    Button1: TButton;
    prvbtn: TButton;
    btnTambah: TButton;
    btnBatal: TButton;
    Panel2: TPanel;
    lblKabkot: TLabel;
    lblKec: TLabel;
    lblDesa: TLabel;
    Panel3: TPanel;
    Label1: TLabel;
    lblJml: TLabel;
    cxGrid1TableView1Column15: TcxGridColumn;
    Label25: TLabel;
    Labelcuy: TLabel;
    JvThread1: TJvThread;
    JvThreadSimpleDialog1: TJvThreadSimpleDialog;
    Memo1: TMemo;
    labelTunggu: TLabel;
    cxGrid2: TcxGrid;
    cxGridDBTableView1: TcxGridDBTableView;
    cxGridTableView1: TcxGridTableView;
    cxGridColumn1: TcxGridColumn;
    cxGridColumn2: TcxGridColumn;
    cxGridColumn3: TcxGridColumn;
    cxGridColumn4: TcxGridColumn;
    cxGridColumn5: TcxGridColumn;
    cxGridColumn6: TcxGridColumn;
    cxGridColumn7: TcxGridColumn;
    cxGridColumn8: TcxGridColumn;
    cxGridColumn9: TcxGridColumn;
    cxGridColumn10: TcxGridColumn;
    cxGridColumn11: TcxGridColumn;
    cxGridColumn12: TcxGridColumn;
    cxGridColumn13: TcxGridColumn;
    cxGridColumn14: TcxGridColumn;
    cxGridColumn15: TcxGridColumn;
    cxGridColumn16: TcxGridColumn;
    cxGridColumn17: TcxGridColumn;
    cxGridColumn18: TcxGridColumn;
    cxGridColumn19: TcxGridColumn;
    cxGridLevel1: TcxGridLevel;
    cxGridTableView1Column1: TcxGridColumn;
    cxGrid1TableView1Column20: TcxGridColumn;
    qryCekTps: TZQuery;
    btnCek: TButton;
    threadCek: TJvThread;
    threadDialogCek: TJvThreadSimpleDialog;
    cboPilgub: TCheckBox;
    function GetCharFromVirtualKey(Key: Word): String;
    procedure btnBatalClick(Sender: TObject);
    procedure FormClose(Sender: TObject; var Action: TCloseAction);
    procedure FormCreate(Sender: TObject);
    procedure btnTambahClick(Sender: TObject);
    procedure cxGrid1TableView1NavigatorButtonsButtonClick(Sender: TObject;
      AButtonIndex: Integer; var ADone: Boolean);
    procedure Timer1Timer(Sender: TObject);
    procedure cxGrid1TableView1EditKeyDown(Sender: TcxCustomGridTableView;
      AItem: TcxCustomGridTableItem; AEdit: TcxCustomEdit; var Key: Word;
      Shift: TShiftState);
    procedure cxGrid1TableView1KeyPress(Sender: TObject; var Key: Char);
    procedure KeyOnlyNum(Sender: TObject; var Key: Char);
    procedure CekDobel();
    function Hitung(tgl:string):Integer;
    procedure Button1Click(Sender: TObject);
    procedure prvbtnClick(Sender: TObject);
    procedure JvThread2FinishAll(Sender: TObject);
    procedure JvThread2Execute(Sender: TObject; Params: Pointer);
    procedure JvThread1Execute(Sender: TObject; Params: Pointer);
    procedure JvThread1FinishAll(Sender: TObject);
    procedure update;
    procedure cxGrid1TableView1DataControllerRecordChanged(
      ADataController: TcxCustomDataController; ARecordIndex,
      AItemIndex: Integer);
    function getTpsId(nama_tps:string): String;
    procedure cxGrid1TableView1DataControllerDataChanged(Sender: TObject);
    procedure Button2Click(Sender: TObject);
    procedure btnCekClick(Sender: TObject);
    procedure threadCekExecute(Sender: TObject; Params: Pointer);
    procedure threadCekFinishAll(Sender: TObject);
    procedure cxGrid1TableView1CustomDrawCell(
      Sender: TcxCustomGridTableView; ACanvas: TcxCanvas;
      AViewInfo: TcxGridTableDataCellViewInfo; var ADone: Boolean);
  private
    { Private declarations }
  public
    { Public declarations }
    constructor Create(AOwner: TComponent; desa: String; proses:integer; user:string); overload;
    Function cekForm(idx:Integer) : Boolean;
    Function cekform2(idx:integer) : boolean;
    Function getTgl(idx:integer) : String;
    Function cekRTRW(kata:String) : String;
    Function getVal(idx:integer; col:integer) : String;
    Function perbaikiTgl(tanggal:string) : String;
  end;

var
  gagal1, gagal2, gagal12: TStringList;
  proses_sekarang: integer;
  Form_TambahPemilih: TForm_TambahPemilih;
  sdesa, skec, skabkot, stps, sjml, spemilih, username: String;
  sfile : string;
implementation

{$R *.dfm}

procedure TForm_TambahPemilih.btnBatalClick(Sender: TObject);
begin
  Close;
end;

procedure TForm_TambahPemilih.FormClose(Sender: TObject;
  var Action: TCloseAction);
begin
{  cxgrid1tableview1.ClearItems;
  jvthread1.Free;
  jvthread2.free;
  timer1.Destroy;}
  //cxgrid1.Destroy;

  Action:=caFree;
end;

procedure TForm_TambahPemilih.FormCreate(Sender: TObject);
var
  Setting: TSetting_Form;
  ntps, ikabkot, ikec, idesa, ndesa: String;
  i, idx: integer;
begin
  Setting := TSetting_Form.Create;
  ZConnection1.HostName := Setting.host;
  ZConnection1.Protocol := Setting.Protocol;
  ZConnection1.Database := Setting.Database;
  ZConnection1.User := Setting.User;
  ZConnection1.Password := Setting.Password;
  ZConnection1.LoginPrompt := False;
  ZConnection1.Connected := True;
  ZQuery1.Connection := ZConnection1;
  ZTable1.Connection := ZConnection1;
  ZQuery2.Connection := ZConnection1;
  qryCek.Connection := ZConnection1;
  qryCekTps.Connection := ZConnection1;
  //
  WindowState:=wsMaximized;
  with ZQuery1 do
  begin
    active := False;
    sql.Clear;
    sql.Text := 'SELECT * FROM desa WHERE KODE_DESA=' + QuotedStr(sdesa);
    active := True;
    first;
    idesa := FieldByName('TAMPIL').AsString;
    ikec := FieldByName('KODE_KECAMATAN').AsString;
    ikabkot := FieldByName('KODE_KABKOT').AsString;
    //
    //
    active:=false;
    sql.Clear;
    sql.Text:='SELECT * FROM kecamatan WHERE KODE_KECAMATAN='+QuotedStr(ikec);
    active:=true;
    first;
    ikec:=FieldByName('TAMPIL').AsString;
    //
    active:=false;
    sql.Clear;
    sql.Text:='SELECT * FROM kabkot WHERE KODE='+QuotedStr(ikabkot);
    active:=true;
    first;
    ikabkot:=FieldByName('TAMPIL').AsString;
    //
    lblKabkot.Caption:='Kabupaten/Kota: '+ikabkot;
    lblKec.Caption:='Kecamatan: '+ikec;
    lblDesa.Caption:='Kelurahan/Desa: '+idesa;
  end;
  //cxGrid1TableView1Column5.Properties.
  lbljml.caption:='';

  //isi tabel contoh
  cxGrid2.BeginUpdate;
  cxGridTableView1.DataController.RecordCount:=1;
  //update masing-masing kolom
  cxGridTableView1.DataController.SetValue(0,0,'3279026705900004');
  cxGridTableView1.DataController.SetValue(0,1,'3210012802070007');
  cxGridTableView1.DataController.SetValue(0,2,'UDIN');
  cxGridTableView1.DataController.SetValue(0,3,'PRIANGAN');
  cxGridTableView1.DataController.SetValue(0,4,'24-08-1971');
  cxGridTableView1.DataController.SetValue(0,5,'L');
  cxGridTableView1.DataController.SetValue(0,6,'B');
  cxGridTableView1.DataController.SetValue(0,7,'ICIH');
  cxGridTableView1.DataController.SetValue(0,8,'LAINNYA');
  cxGridTableView1.DataController.SetValue(0,9,'JALAN PERJUANGAN');
  cxGridTableView1.DataController.SetValue(0,10,'001');
  cxGridTableView1.DataController.SetValue(0,11,'001');
  cxGridTableView1.DataController.SetValue(0,12,'CIBODAS');
  cxGridTableView1.DataController.SetValue(0,13,'-');
  cxGridTableView1.DataController.SetValue(0,14,'005');
  cxGrid2.EndUpdate;
end;

function TForm_TambahPemilih.Hitung(tgl:string):Integer;
var
  acuan,thn: String;
  hari, bulan, tahun, hari_acuan, bulan_acuan, tahun_acuan, usia: Integer;
  temp: TStrings;
begin
  with ZQuery1 do begin
      Active:=false;
      sql.Clear;
      SQL.Text:='SELECT * FROM info_tanggal WHERE AKTIF = 1';
      Active:=true;
      acuan := formatDateTime('mm/dd/yyyy',fieldByName('TANGGAL').AsDateTime);
    end;
  //showMessage(acuan);
  temp := TStringList.Create;
  try
      ExtractStrings(['/'], [], PChar(acuan), temp);
      if(temp.Count < 3) then begin
        temp := TStringList.Create;
        ExtractStrings(['-'], [], PChar(acuan), temp);
      end;
//      showmessage(temp[1]);
      hari_acuan := StrToInt(temp[1]);
      bulan_acuan := StrToInt(temp[0]);
      tahun_acuan := StrToInt(temp[2]);
    finally
      temp.Free;
    end;
  hari := 0;
  bulan:= 0;
  tahun:= 0;

  if ((tgl <> '') and (tgl <> '00-00-0000')) then begin
    temp := TStringList.Create;
  try
      ExtractStrings(['-'], [], PChar(tgl), temp);
//      showmessage(temp[1]);
      hari := StrToInt(temp[0]);
      bulan := StrToInt(temp[1]);
      tahun := StrToInt(temp[2]);
    finally
      temp.Free;
    end;

    usia := tahun_acuan - tahun;
    if(bulan_acuan < bulan) then
      usia := usia - 1
    else if(bulan_acuan = bulan) then begin
      if(hari_acuan < hari) then
        usia:= usia -1;
    end;
    if(bulan > 12) then
      usia:= -1;
    result:= usia;
    //txtUsia.Text:= IntToStr(usia);
  end else result:= -1;
end;

procedure TForm_TambahPemilih.btnTambahClick(Sender: TObject);
var
  buttonSelected,i,succ,iterate,usia,cek : Integer;
  tanggal,idtgl,que,idorang,idtabel, kter:String;
  status1,message,kawin,kelamin,kelaminfull,namalengkap,elantara,tps_id:string;
  dobel2, statusbenar, kelaminbenar :boolean;
  listgagal, elemen: Tstringlist;
begin
  kter := '';
  if(cboPilgub.Checked = true) then
    kter := 'PILGUB';
 // ShowMessage(cxGrid1TableView1.DataController.Values[0,4]);
 labelTunggu.Visible:=true;
 listgagal := TStringList.Create;
 statusbenar:=true;
 kelaminbenar:=true;
 dobel2:=true;
 if proses_sekarang = 8 then
    status1 := '1'
 else if proses_sekarang = 4 then
    status1 := '3'
  else
    status1 := '0';
  //cek di awal beud
  //showmessage('ough');
  for i:=0 to cxGrid1TableView1.DataController.RecordCount-1 do begin
    namalengkap:= AnsiUpperCase(getVal(i,2));
      //usia := hitung(getTgl(i));
    usia := hitung(perbaikiTgl(getVal(i,4)));
    kelaminfull := AnsiUpperCase(getVal(i,5));
    kelamin := AnsiUpperCase(Copy(getVal(i,5),1,1));
    kawin :=  AnsiUpperCase(Copy(getVal(i,6),1,1));
    if((namalengkap <> '') and (copy(getVal(i,14),0,1) <> 'K')) then
    begin
      if(((usia < 17) AND (kawin = 'B')) OR (usia = -1)) then begin
        //showmessage('gagal');
        listgagal.Add(AnsiUpperCase(getVal(i,2)));
      end;
      if((kawin<>'B') AND (kawin<>'S') AND (kawin<>'P')) then begin
        statusbenar:=false;
        break;
      end;
      if(((kelamin<>'L') AND (kelamin<>'P')) OR (kelaminfull = 'PRIA')) then begin
        kelaminbenar:=false;
        break;
      end;
      dobel2:=cekForm2(i);
      if not dobel2 then break;
      //showmessage(inttostr(usia));
    end;
        //showmessage('ough');
  end;

  if ((listgagal.count = 0) and dobel2 and statusbenar and kelaminbenar) then begin
    //showmessage('oughberhasil');
    buttonSelected := MessageDlg('Apakah anda yakin akan menambah pemilih baru?',mtConfirmation , mbOKCancel, 0);
    if buttonSelected = mrOK  then begin
    with ZQuery1 do  //masukkin nih gan
          begin
            //pemilih
            Active:=False;
            sql.Clear;
            que := 'CREATE TABLE IF NOT EXISTS pemilih_'+sdesa+'('+
                          'ID_USER int(11) NOT NULL AUTO_INCREMENT,'+
                          'NIK char(36) NOT NULL,'+
                          'NKK char(36) NOT NULL,'+
                          'NAMA char(50) NOT NULL,'+
                          'TEMPAT char(36) NOT NULL,'+
                          'TANGGAL char(10) NOT NULL,'+
                          'IBU char(36) NOT NULL,'+
                          'AGAMA char(36) NOT NULL,'+
                          'KAWIN char(1) NOT NULL,'+
                          'KELAMIN char(1) NOT NULL,'+
                          'KELAINAN char(36) NOT NULL,'+
                          'ALAMAT char(150) NOT NULL,'+
                          'RW char(3) NOT NULL,'+
                          'RT char(3) NOT NULL,'+
                          'DUSUN char(30) NOT NULL,'+
                          'KET char(150) NOT NULL,'+
                          'ID_TANGGAL int(11) NOT NULL,'+
                          'TPS int(11) NOT NULL,'+
                          'STATUS1 char(1) NOT NULL,'+
                          'STATUS2 char(1) NOT NULL,'+
                          'GANDA char(1) NOT NULL,'+
                          'STATUS3 char(1) NOT NULL,'+
                          'STATUSP char(1) NOT NULL,'+
                          'ALASANP char(1) NOT NULL,'+
                          'CACAT char(1) NOT NULL,'+
                          'PENDIDIKAN char(1) NOT NULL,'+
                          'PEKERJAAN char(1) NOT NULL,'+
                          'STATUSR char(1) NOT NULL,'+
                          'WN char(1) NOT NULL,'+
                          'PRIMARY KEY (ID_USER))';
         //   showmessage(que);
            sql.text:=que;
            ExecSQL;
            //penyimpan
            Active:=False;
            sql.Clear;
            //ubah
            sql.Text := 'INSERT IGNORE INTO penyimpan (NAMA,UPLOAD) VALUES ("pemilih_'+sdesa+'",'+QuotedStr('')+')';
            ExecSQL;
          end;
          tanggal := FormatDateTime('yyyy-mm-dd hh:mm:ss', Now());
      with ZQuery1 do  //masukkin nih gan
        begin
          Active:=False;
          sql.Clear;
          sql.Text := 'INSERT INTO tanggal (TANGGAL) VALUES ("'+tanggal+'")';
          ExecSQL;
        end;
      with ZQuery1 do  //masukkin nih gan
        begin
          Active:=False;
          sql.Clear;
          sql.Text := 'SELECT * FROM tanggal ORDER BY ID_TANGGAL DESC';
          Active:=True;
          idtgl := FieldByName('ID_TANGGAL').AsString;  //dapat ID_TGL
        end;
    //baca record
    succ:=0;
    for i:=0 to cxGrid1TableView1.DataController.RecordCount-1 do begin
      //cek kelengkapan
      if (cekForm(i) and dobel2) then begin
      //showmessage(copy(getVal(i,0),1,36));
  //if (1+1=2) then begin
        //tulis
          //tangani dulu
          cek:= 0;
          elemen := TStringList.Create;
          while cek < 15 do begin
            elantara := getVal(i,cek);
            elantara := StringReplace(elantara, '''', '',[rfReplaceAll, rfIgnoreCase]);
            elantara := StringReplace(elantara, '\', '',[rfReplaceAll, rfIgnoreCase]);
            elemen.Add(elantara);
            //showmessage(elemen[cek]);
            cek := cek+1;
          end;

          tps_id := getTpsId(elemen[14]);
          //showMessage(tps_id);

          que:=QuotedStr(copy(elemen[0],1,36))+','+
            QuotedStr(copy(elemen[1],1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[2]),1,50))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[3]),1,36))+','+
            QuotedStr(perbaikiTgl(elemen[4]))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[7]),1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[8]),1,36))+','+
            QuotedStr(Copy(AnsiUpperCase(StringReplace(elemen[6], ' ', '',[rfReplaceAll, rfIgnoreCase])),1,1))+','+
            QuotedStr(Copy(AnsiUpperCase(StringReplace(elemen[5], ' ', '',[rfReplaceAll, rfIgnoreCase])),1,1))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[13]),1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[9]),1,150))+','+
            QuotedStr(cekRTRW(elemen[11]))+','+
            QuotedStr(cekRTRW(elemen[10]))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[12]),1,30))+','+
            QuotedStr(kter)+','+
            idtgl+','+
            quotedStr(tps_id)+','+
            QuotedStr(status1)+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0');
            //showmessage(que);
        with zquery1 do begin
          active:=false;
          sql.Clear;
          que:='INSERT INTO pemilih_'+sdesa+' (NIK,NKK,NAMA,TEMPAT,TANGGAL,IBU,AGAMA,KAWIN,KELAMIN,KELAINAN,ALAMAT,RW,RT,DUSUN,KET,ID_TANGGAL,TPS,STATUS1,STATUS2,GANDA,STATUS3,STATUSP,CACAT,PENDIDIKAN,PEKERJAAN,STATUSR,WN) VALUES ('+que+')';
          //ShowMessage(que);
          sql.text:=que;
          ExecSQL;
        end;
      with zquery2 do begin
        //ambil id orang yang baru dimasukin
        Active:=false;
        Sql.Clear;
        Sql.Text:='SELECT MAX(ID_USER) AS MAX FROM pemilih_'+sdesa;
        Active:=True;
        idorang := FieldByName('MAX').AsString;
      end;
      with zquery2 do begin
        //ambil id tabelnya yang baru dimasukin
        Active:=false;
        Sql.Clear;
        Sql.Text:='SELECT ID FROM penyimpan WHERE NAMA LIKE '+QuotedStr('pemilih_'+sdesa);
        Active:=True;
        idtabel := FieldByName('ID').AsString;
      end;
      que:= QuotedStr(idtabel+'-'+idorang)+','+
            QuotedStr(copy(elemen[0],1,36))+','+
            QuotedStr(copy(elemen[1],1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[2]),1,50))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[3]),1,36))+','+
            QuotedStr(perbaikiTgl(elemen[4]))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[7]),1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[8]),1,36))+','+
            QuotedStr(Copy(AnsiUpperCase(StringReplace(elemen[6], ' ', '',[rfReplaceAll, rfIgnoreCase])),1,1))+','+
            QuotedStr(Copy(AnsiUpperCase(StringReplace(elemen[5], ' ', '',[rfReplaceAll, rfIgnoreCase])),1,1))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[13]),1,36))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[9]),1,150))+','+
            QuotedStr(cekRTRW(elemen[11]))+','+
            QuotedStr(cekRTRW(elemen[10]))+','+
            QuotedStr(copy(AnsiUpperCase(elemen[12]),1,30))+','+
            QuotedStr('')+','+
            idtgl+','+
            '0,'+
            QuotedStr(status1)+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr('0')+','+
            QuotedStr(username)+','+
            QuotedStr('1');
      with zquery2 do begin
         //masukin ke tabel history
         active:=false;
          sql.Clear;
          que:='INSERT INTO history (ID_USER,NIK,NKK,NAMA,TEMPAT,TANGGAL,IBU,AGAMA,KAWIN,KELAMIN,KELAINAN,ALAMAT,RW,RT,DUSUN,KET,ID_TANGGAL,TPS,STATUS1,STATUS2,GANDA,STATUS3,STATUSP,CACAT,PENDIDIKAN,PEKERJAAN,STATUSR,WN,USERNAME,KET_AKSI) VALUES ('+que+')';
          //ShowMessage(que);
          sql.text:=que;
          ExecSQL;
      end;
        inc(succ);
      end else if (not dobel2) then
        break;

    end;
    if (dobel2) then begin
      ShowMessage('Berhasil menambahkan pemilih sebanyak '+IntToStr(succ)+' orang');
      Close;
    end;
  end;
  end
  else begin
    //showmessage('oughgagal');
    if listgagal.count > 0 then begin
      message := 'Data gagal dimasukkan karena masih di bawah umur dan belum menikah, atau format tanggal lahir tidak sesuai:'+AnsiString(#13#10);
      //showmessage('sadf');
      for iterate := 0 to listgagal.count-1 do begin
        message := message +' - '+ listgagal[iterate]+AnsiString(#13#10);
      end;
      message := message + 'Silakan periksa kembali data yang akan dimasukkan';
       showmessage(message);
    end else if not statusbenar then
      showmessage('Ada isian status perkawinan dengan format yang salah. Mohon isi dengan "B", "S", atau "P"')
    else if not kelaminbenar then
      showmessage('Ada isian jenis kelamin dengan format yang salah. Mohon isi dengan "L", atau "P"');
  end;
  labelTunggu.Visible:=false;
end;

Function TForm_TambahPemilih.cekform2(idx:integer) : boolean;
var
  sTemp:Boolean;
  nama, nik : string;
  tanggallahir: string;
  query, message : string;
  current, dobel, buttonselected : integer;
begin
  sTemp:=true;
  with cxGrid1TableView1.DataController do begin
    if ((Values[idx,0]<>null) and (Values[idx,2]<>null) and (Values[idx,3]<>null) and (Values[idx,4]<>null) and (Values[idx,6]<>null) and (Values[idx,10]<>null) and (Values[idx,11]<>null)) then begin
      stemp:=true;
      dobel:=0;
      nik := Values[idx,0];
      nama := Values[idx,2];
      tanggallahir := perbaikiTgl(Values[idx,4]);
      //getTgl(current);

      if(nik <> '0') then begin
        with qryCek do
        begin
          Active:=false;
          sql.Clear;
          query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NIK = '+quotedStr(nik)+' AND STATUS2 = ''0'' LIMIT 0,1';
          SQL.Text:=query;
          Active:=true;
          if(recordCount > 0) then
            dobel := 1;
        end;
      end;

      with qryCek do
      begin
        Active:=false;
        sql.Clear;
        query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NAMA = '+quotedStr(AnsiUpperCase(StringReplace(nama,'''',' ',[rfReplaceAll])))+' AND TANGGAL = '+quotedStr(tanggallahir)+' AND STATUS2 = ''0'' LIMIT 0,1';
        SQL.Text:=query;
        Active:=true;
        if(recordCount > 0) then
          dobel := 2;
      end;

      with qryCek do
      begin
        Active:=false;
        sql.Clear;
        query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NAMA = '+quotedStr(AnsiUpperCase(StringReplace(nama,'''',' ',[rfReplaceAll])))+' AND NIK = '+quotedStr(nik)+' AND STATUS2 = ''0'' LIMIT 0,1';
        SQL.Text:=query;
        Active:=true;
        if(recordCount > 0) then
          dobel := 3;
      end;
      if(dobel>0) then begin
      case dobel of
      1:
        message := 'Ditemukan data dengan NIK sama: '+nik+' pada database. ';
      2:
        message := 'Ditemukan data dengan NAMA dan TANGGAL LAHIR sama: '+AnsiUpperCase(nama)+' pada database. ';
      3:
        message := 'Ditemukan data dengan NIK, NAMA dan TANGGAL LAHIR sama: '+AnsiUpperCase(nama)+' pada database. ';
      else message := '';
      end;
      message := message + 'Apakah anda tetap akan menambah data?';
      buttonSelected := MessageDlg(message,mtConfirmation , mbOKCancel, 0);
      if(buttonSelected = mrCancel) then begin
    //showmessage('dihapus');
        stemp:=false;
      end;
      end;
    end;
  end;
  result:=stemp;
end;

Function TForm_TambahPemilih.cekForm(idx:Integer) : Boolean;
var
  sTemp:Boolean;
  nama, nik : string;
  tanggallahir: string;
  query, message : string;
  current, dobel, buttonselected : integer;
begin
  sTemp:=False;
  with cxGrid1TableView1.DataController do begin
    if(Values[idx,0] = '') then
      Values[idx,0] := '0';
    if ((Values[idx,0]<>'') and (Values[idx,2]<>'') and (Values[idx,3]<>'') and (Values[idx,4]<>'') and (Values[idx,6]<>'') and (Values[idx,10]<>'') and (Values[idx,11]<>'')) then begin
      stemp:=true;

  //cxGrid1TableView1.Controller.SelectedRows[current].Destroy;
  //showmessage(nik);
  //hello
    end
    else
    if((copy(Values[idx,14],0,1) = 'K') and (Values[idx,2]<>'') and (Values[idx,5]<>'')) then
      stemp:=true;
  end;
  Result := sTemp;
end;

Function TForm_TambahPemilih.perbaikiTgl(tanggal:string) : String;
var
  list_tgl, list_tgl2 : TStringList;
  hari_acuan, bulan_acuan, tahun_acuan, temp: string;
begin
  //jadikan stringlist
  list_tgl := TStringList.Create;
  list_tgl2 := TStringList.Create;
  try
      ExtractStrings(['-'], [], PChar(tanggal), list_tgl);
      if(list_tgl.Count < 3) then begin //asumsinya, kalo ga d-m-Y ya d/m/Y
        ExtractStrings(['/'], [], PChar(tanggal), list_tgl2);
        if(list_tgl2.Count = 3) then begin
          hari_acuan := (list_tgl2[0]);
          bulan_acuan := (list_tgl2[1]);
          tahun_acuan := (list_tgl2[2]);
        end else begin
          hari_acuan :='00';
          bulan_acuan :='00';
          tahun_acuan :='0000';
        end;
      end
//      showmessage(temp[1]);
      else begin
        hari_acuan := (list_tgl[0]);
        bulan_acuan := (list_tgl[1]);
        tahun_acuan := (list_tgl[2]);
      end;
    finally
      list_tgl.Free;
      list_tgl2.Free;
    end;

    if(length(hari_acuan) = 1) then
      hari_acuan := '0'+hari_acuan;
    if(length(bulan_acuan) = 1) then
      bulan_acuan := '0'+bulan_acuan;
    if(length(tahun_acuan) = 2) then
      tahun_acuan := '19'+tahun_acuan;
  temp:=hari_acuan+'-'+bulan_acuan+'-'+tahun_acuan;
  result:=temp;
end;

Function TForm_TambahPemilih.getTgl(idx:integer) : String;
var
  sTemp,tgl,bln,thn:String;
  tgls:TDateTime;
  selisih:integer;
  temp:TStrings;
begin
  if (cxGrid1TableView1.DataController.Values[idx,4]<>null) then begin
    sTemp:=cxGrid1TableView1.DataController.Values[idx,4];
    tgls:=strtodatetime(cxGrid1TableView1.DataController.Values[idx,4]);
    temp := TStringList.Create;
    try
      ExtractStrings(['/'], [], PChar(stemp), temp);
      tgl := temp[1];
      bln := temp[0];
      thn := temp[2];
    finally
      temp.Free;
    end;
    sTemp:=tgl+'-'+bln+'-'+thn;
    sTemp:=FormatDateTime('dd-mm-yyyy', tgls);
    //ShowMessage(stemp);
    Result := sTemp;
  end;
end;

Function TForm_TambahPemilih.cekRTRW(kata:String) : String;
var
  stemp1, stemp:String;
begin
  stemp1 := StringReplace(kata,' ','',[rfReplaceAll]);
  sTemp:='';
  if (Length(stemp1) = 0) then
    sTemp:='000'
  else if (Length(stemp1)=1) then
    sTemp:='00'+stemp1
  else if (Length(stemp1)=2) then
    sTemp:='0'+stemp1
  else if (Length(stemp1)>3) then
    sTemp:=Copy(stemp1, Length(stemp1)-3, 3)
  else
    sTemp:=stemp1;
  Result := sTemp;
end;

Function TForm_TambahPemilih.getVal(idx:integer; col:integer) : String;
var
  stemp:String;
begin
  sTemp:='';
  if (cxGrid1TableView1.DataController.Values[idx,col]<>null) then
    sTemp:=cxGrid1TableView1.DataController.Values[idx,col];
  Result := sTemp;
end;

constructor TForm_TambahPemilih.Create(AOwner: TComponent; desa: String; proses:integer; user:String);
begin
  username:=user;
  proses_sekarang := proses;
  sdesa := desa;
  //showmessage(sdesa);
  inherited Create(AOwner);
end;

procedure TForm_TambahPemilih.cxGrid1TableView1NavigatorButtonsButtonClick(
  Sender: TObject; AButtonIndex: Integer; var ADone: Boolean);
begin
  lblJml.Caption:=IntToStr(cxGrid1TableView1.DataController.RecordCount+1);
end;

procedure TForm_TambahPemilih.Timer1Timer(Sender: TObject);
begin
  if(Labelcuy.Visible = true) then
    Labelcuy.Visible := false
  else
    Labelcuy.Visible := true;
end;

procedure TForm_TambahPemilih.cxGrid1TableView1EditKeyDown(
  Sender: TcxCustomGridTableView; AItem: TcxCustomGridTableItem;
  AEdit: TcxCustomEdit; var Key: Word; Shift: TShiftState);
var
tempat : integer;
keys : String;
begin
  if(key = VK_RETURN) then begin
    //showMessage('aw');
    cxGrid1TableView1.DataController.Append;
    cekDobel();
    lblJml.Caption:=IntToStr(cxGrid1TableView1.DataController.RecordCount);
  end
  else if(key = VK_TAB) then  begin
    //showMessage('iw');
    if(cxGrid1TableView1.Controller.FocusedColumnIndex < cxGrid1TableView1.ColumnCount) then
      cxGrid1TableView1.Controller.FocusedColumnIndex := cxGrid1TableView1.Controller.FocusedColumnIndex+1
    else
      cxGrid1TableView1.Controller.FocusedColumnIndex := cxGrid1TableView1.Controller.FocusedColumnIndex;
    //showMessage(inttostr(cxGrid1TableView1.Controller.FocusedColumnIndex));
  end;

end;

procedure TForm_TambahPemilih.CekDobel();
var
  nama, nik : string;
  tanggallahir: string;
  query, message : string;
  current, dobel, buttonselected : integer;
begin
  current := cxGrid1TableView1.DataController.RecordCount-1;
  nik := getVal(current,0);
  nama := getVal(current,2);
  //getTgl(current);

  with qryCek do
  begin
    Active:=false;
    sql.Clear;
    query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NIK = '+quotedStr(nik)+' LIMIT 0,1';
    SQL.Text:=query;
    Active:=true;
    if(recordCount > 0) then
      dobel := 1;
  end;

  with qryCek do
  begin
    Active:=false;
    sql.Clear;
    query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NAMA = '+quotedStr(AnsiUpperCase(nama))+' AND TANGGAL = '+quotedStr(tanggallahir)+' LIMIT 0,1';
    SQL.Text:=query;
    Active:=true;
    if(recordCount > 0) then
      dobel := 2;
  end;

  with qryCek do
  begin
    Active:=false;
    sql.Clear;
    query:='SELECT ID_USER FROM pemilih_'+sdesa+' WHERE NAMA = '+quotedStr(AnsiUpperCase(nama))+' AND NIK = '+quotedStr(nik)+' LIMIT 0,1';
    SQL.Text:=query;
    Active:=true;
    if(recordCount > 0) then
      dobel := 3;
  end;
  if(dobel>0) then begin
  case dobel of
  1:
    message := 'Ditemukan data dengan NIK sama: '+nik+' pada database. ';
  2:
    message := 'Ditemukan data dengan NAMA dan TANGGAL LAHIR sama: '+AnsiUpperCase(nama)+' pada database. ';
  3:
    message := 'Ditemukan data dengan NIK, NAMA dan TANGGAL LAHIR sama: '+AnsiUpperCase(nama)+' pada database. ';
  else message := '';
  end;
  message := message + 'Apakah anda tetap akan menambah data?';
  buttonSelected := MessageDlg(message,mtConfirmation , mbOKCancel, 0);
  if(buttonSelected = mrCancel) then begin
    //showmessage('dihapus');
    cxGrid1TableView1.DataController.RecordCount := current-1;
  end;
  //cxGrid1TableView1.Controller.SelectedRows[current].Destroy;
  //showmessage(nik);
  //hello
  end;
end;

procedure TForm_TambahPemilih.KeyOnlyNum(Sender: TObject; var Key: Char);
var
  cari:char;
begin
  //cari := Key[1];
  if not(Key in [#8, '0' .. '9'])  then
  begin
    Key := #0;
  end;
end;

function TForm_TambahPemilih.GetCharFromVirtualKey(Key: Word): String;
var
  keyboardState: TKeyboardState;
  asciiResult: Integer;
begin
  GetKeyboardState(keyboardState) ;

  SetLength(Result, 2) ;
  asciiResult := ToAscii(key, MapVirtualKey(key, 0), keyboardState, @Result[1], 0) ;
  case asciiResult of
    0: Result := '';
    1: SetLength(Result, 1) ;
    2:;
    else
      Result := '';
  end;
end;

procedure TForm_TambahPemilih.cxGrid1TableView1KeyPress(Sender: TObject;
  var Key: Char);
var tempat : integer;
begin
  begin
    //showMessage(inttostr(cxGrid1TableView1.Controller.FocusedColumnIndex));
    tempat :=cxGrid1TableView1.Controller.FocusedColumnIndex;
    if(tempat = 0) then
    begin
      KeyOnlyNum(Sender, Key);
    end;
    //KeyOnlyNum(Sender, Key);
  end;
end;

procedure TForm_TambahPemilih.Button1Click(Sender: TObject);
var
  openDialog : TOpenDialog;    // Open dialog variable
begin
  // Create the open dialog object - assign to our open dialog variable
  openDialog := TOpenDialog.Create(self);

  // Set up the starting directory to be the current one
  openDialog.InitialDir := GetCurrentDir;

  // Only allow existing files to be selected
  openDialog.Options := [ofFileMustExist];

  // Allow only .dpr and .pas files to be selected
  openDialog.Filter := 'Excel files|*.xls';
   // 'Delphi project files|*.dpr|Delphi pascal files|*.pas';

  // Select pascal files as the starting filter type
  //openDialog.FilterIndex := 2;

  // Display the open file dialog
  if openDialog.Execute
  then
  begin
    //ShowMessage('File : '+openDialog.FileName);
    sfile:=openDialog.FileName;
    fileloc.Text:=openDialog.FileName;
  end;

  // Free up the dialog
  openDialog.Free;
end;

procedure TForm_TambahPemilih.prvbtnClick(Sender: TObject);
const
  xlCellTypeLastCell = $0000000B;
var
  asik:integer;
  XLApp, Sheet: OLEVariant;
  RangeMatrix: Variant;
  x, y, y1, k, r,a: Integer;
begin
  if(sfile<>'')then
  begin
    labelTunggu.Visible:=true;
    with cxGrid1TableView1.DataController do
    begin
      BeginUpdate;
      try
        while RecordCount > 0 do
          DeleteRecord(0);
      finally
        EndUpdate;
      end;
      beginupdate;
      RecordCount:=0;
      endupdate;
    end;
    //showmessage('ahiy');
    {JvThread2.ThreadDialog := JvThreadSimpleDialog2;
    JvThread2.ExecuteAndWait(Self);}
    //memo1.Text:=memo1.Text+'1';
    XLApp := CreateOleObject('Excel.Application');
    try
 //     showmessage('2');
      //memo1.Text:=memo1.Text+'2';
      XLApp.Visible := False;
      XLApp.Workbooks.Open(sFile);
      Sheet := XLApp.Workbooks[ExtractFileName(sFile)].WorkSheets[1];
      Sheet.Cells.SpecialCells(xlCellTypeLastCell, EmptyParam).Activate;
      x := XLApp.ActiveCell.Row;
      y1 := XLApp.ActiveCell.Column;
      y := 15;
      a:=0;
      RangeMatrix := XLApp.Range['A1', XLApp.Cells.Item[X, Y1]].Value;
      //showmessage('3');
      //memo1.Text:=memo1.Text+'3';
      //cxGrid1TableView1.ColumnCount:=y;
      cxGrid1TableView1.BeginUpdate;
      cxGrid1TableView1.DataController.RecordCount:=x-1;
      {while a < x-1 do begin
        cxGrid1TableView1.DataController.InsertRecord(a);
        a:=a+1;
      end;}
      cxGrid1TableView1.EndUpdate;
      labelTunggu.Visible:=false;
      sleep(100);
      labelTunggu.Visible:=true;
      lblJml.Caption:=inttostr(x-1);
      //sleep(200);
//      preview.ColCount:=y;
//      preview.RowCount:=x;
      {for r := 0 to y do
        begin
        preview.Cells[r,0]:=Chr(65+r);


        end;}
     //   showmessage('4');
      //memo1.Text:=memo1.Text+'4';
      k := 1;
      if y1 > 15 then
        y := 15
      else
        y:=y1;
   //     showmessage('5');
      //memo1.Text:=memo1.Text+'5';
      labelTunggu.Visible:=false;
      sleep(100);
      labelTunggu.Visible:=true;
      cxGrid1TableView1.BeginUpdate;
      cxGrid1TableView1.DataController.BeginFullUpdate;
      repeat
        for r := 1 to y do
        begin
          //this section to operate data, change as your need
          cxGrid1TableView1.DataController.SetValue(k-1,r-1,StringReplace(RangeMatrix[K+1, R],'\','',[rfReplaceAll]));
          cxGrid1TableView1.DataController.SetValue(k-1,15,'0');
          //preview.Cells[r-1,k]:=RangeMatrix[K, R];
        end;
        Inc(k, 1);
      until ((k >= x));
      //sleep(100);
      cxGrid1TableView1.DataController.endFullUpdate;
      cxGrid1TableView1.EndUpdate;

      RangeMatrix := Unassigned;

///      showmessage('6');
      //memo1.Text:=memo1.Text+'6';
    finally
      if not VarIsEmpty(XLApp) then
      begin
        XLApp.Quit;
        XLAPP := Unassigned;
        Sheet := Unassigned;
      end;
    end;
    labelTunggu.Visible:=false;
  end
  else
    ShowMessage('Anda belum memilih file');
end;

procedure TForm_TambahPemilih.update;
begin
  //coba
  cxGrid1.BeginUpdate;
  cxGrid1.EndUpdate;
end;

procedure TForm_TambahPemilih.JvThread2FinishAll(Sender: TObject);
begin
//showmessage('hello_panda');
//atur panjang kolom
  memo1.Text:=memo1.text+'selesai';
  //cxGrid1TableView1.BeginUpdate;
  //cxGrid1TableView1.EndUpdate;
  //sleep(100);
  //JvThread1.ThreadDialog := JvThreadSimpleDialog1;
  //JvThread1.Execute(Self);
  {for column:=0 to 12 do begin
    WMax := 0;
    for i := 0 to (cxGrid1TableView1.DataController.RecordCount - 1) do begin
      W := cxGrid1.Canvas.TextWidth(cxGrid1TableView1.DataController.GetValue(i, column));
      if W > WMax then
        WMax := W;
    end;
    cxGrid1TableView1.Columns[column].Width := WMax + 10;
  end;}
end;

procedure TForm_TambahPemilih.JvThread2Execute(Sender: TObject;
  Params: Pointer);
const
  xlCellTypeLastCell = $0000000B;
var
  asik:integer;
  XLApp, Sheet: OLEVariant;
  RangeMatrix: Variant;
  x, y, y1, k, r,a: Integer;
begin
  //asik := 1+1;
  //masukkan ke sg
  CoInitialize(nil); // <-- manually call CoInitialize()
 //   showmessage('1');
    memo1.Text:=memo1.Text+'1';
    XLApp := CreateOleObject('Excel.Application');
    try
 //     showmessage('2');
      memo1.Text:=memo1.Text+'2';
      XLApp.Visible := False;
      XLApp.Workbooks.Open(sFile);
      Sheet := XLApp.Workbooks[ExtractFileName(sFile)].WorkSheets[1];
      Sheet.Cells.SpecialCells(xlCellTypeLastCell, EmptyParam).Activate;
      x := XLApp.ActiveCell.Row;
      y1 := XLApp.ActiveCell.Column;
      y := 14;
      a:=0;
      RangeMatrix := XLApp.Range['A1', XLApp.Cells.Item[X, Y1]].Value;
      //showmessage('3');
      memo1.Text:=memo1.Text+'3';
      //cxGrid1TableView1.ColumnCount:=y;
      cxGrid1TableView1.BeginUpdate;
      cxGrid1TableView1.DataController.RecordCount:=x-1;
      {while a < x-1 do begin
        cxGrid1TableView1.DataController.InsertRecord(a);
        a:=a+1;
      end;}
      cxGrid1TableView1.EndUpdate;
      lblJml.Caption:=inttostr(x-1);
      //sleep(200);
//      preview.ColCount:=y;
//      preview.RowCount:=x;
      {for r := 0 to y do
        begin
        preview.Cells[r,0]:=Chr(65+r);


        end;}
     //   showmessage('4');
      memo1.Text:=memo1.Text+'4';
      k := 1;
      if y1 > 14 then
        y := 14
      else
        y:=y1;
   //     showmessage('5');
      memo1.Text:=memo1.Text+'5';
      cxGrid1TableView1.BeginUpdate;
      //cxGrid1TableView1.DataController.BeginFullUpdate;
      repeat
        for r := 1 to y do
        begin
          //this section to operate data, change as your need
          cxGrid1TableView1.DataController.SetValue(k-1,r-1,RangeMatrix[K+1, R]);
        end;
        Inc(k, 1);
      until ((k >= x));
      //sleep(100);
      //sleep(1500);
      //cxGrid1TableView1.DataController.endFullUpdate;
      cxGrid1TableView1.EndUpdate;

      RangeMatrix := Unassigned;

///      showmessage('6');
      memo1.Text:=memo1.Text+'6';
    finally
      if not VarIsEmpty(XLApp) then
      begin
        XLApp.Quit;
        XLAPP := Unassigned;
        Sheet := Unassigned;
      end;
    end;
    {for i := 0 to preview.ColCount - 1 do
      AutoSizeCol(preview, i);}



    CoUnInitialize; //
    //jvThread2.Synchronize(update);
    {if JvThread2.Terminated then
  begin
    Exit;
  end;}
end;

procedure TForm_TambahPemilih.JvThread1Execute(Sender: TObject;
  Params: Pointer);
var
  column, i, W, Wmax:integer;
begin
  cxGrid1TableView1.ApplyBestFit;
  {for column:=0 to 12 do begin
    WMax := 0;
    for i := 0 to (cxGrid1TableView1.DataController.RecordCount - 1) do begin
      if(cxGrid1TableView1.DataController.GetValue(i, column) <> null) then
        W := cxGrid1.Canvas.TextWidth(cxGrid1TableView1.DataController.GetValue(i, column));
      if W > WMax then
        WMax := W;
    end;
    cxGrid1TableView1.BeginUpdate;
    cxGrid1TableView1.Columns[column].Width := WMax + 10;
    cxGrid1TableView1.EndUpdate;
  end;}

end;

procedure TForm_TambahPemilih.JvThread1FinishAll(Sender: TObject);
var
  column, i, W, Wmax:integer;
begin
  //1+1 = 2
end;

procedure TForm_TambahPemilih.cxGrid1TableView1DataControllerRecordChanged(
  ADataController: TcxCustomDataController; ARecordIndex,
  AItemIndex: Integer);
begin
  lblJml.Caption := inttostr(cxGrid1TableView1.DataController.RecordCount);
end;

procedure TForm_TambahPemilih.cxGrid1TableView1DataControllerDataChanged(
  Sender: TObject);
begin
  lblJml.Caption := inttostr(cxGrid1TableView1.DataController.RecordCount);
end;

function TForm_TambahPemilih.getTpsId(nama_tps:string): String;
var
  row_tps, jumlah_pemilih : integer;
  hasil, temp_tps, sql_cariTps, sql_insertTps, sql_hitungIsiTps : string;
begin
  //mengambil Id Tps dari Nama Tps yang bersangkutan
  //pertama: dipadding/potong sampai sesuai dengan panjang TPS yang diperlukan (pake cekRTRW ajah)
  temp_tps := cekRTRW(nama_tps);
  if(temp_tps = '000') then begin
    hasil:='0';
  end
  else begin
    //cari tps di database
    sql_cariTps := 'SELECT ID_TPS FROM daftar_tps WHERE NAMA = '+quotedstr(temp_tps)+' AND KODE_DESA = '+quotedStr(sDesa);
    qryCekTps.Active := False;
    qryCekTps.SQL.Clear;
    qryCekTps.SQL.Text := sql_cariTps;
    qryCekTps.Active := True;
    qryCekTps.First;

    //jika tidak ada, insert
    row_tps := qryCekTps.RecordCount;
    if(row_tps < 1) then begin
      sql_insertTps := 'INSERT INTO daftar_tps(NAMA, KODE_DESA, ALAMAT)'
      +' VALUES('+quotedStr(temp_tps)+','+quotedStr(sdesa)+','''')';
      qryCekTps.Active:=False;
      qryCekTps.SQL.Clear;
      qryCekTps.SQL.Text := sql_insertTps;
      qryCekTps.ExecSQL;
    end;

    //pasti sudah ada, sekarang ambil id tps nya
    sql_cariTps := 'SELECT ID_TPS FROM daftar_tps WHERE NAMA = '+quotedstr(temp_tps)+' AND KODE_DESA = '+quotedStr(sDesa);
    qryCekTps.Active := False;
    qryCekTps.SQL.Clear;
    qryCekTps.SQL.Text := sql_cariTps;
    qryCekTps.Active := True;
    qryCekTps.First;

    //return
    while not qryCekTps.Eof do begin
      hasil := qryCekTps.fieldByName('ID_TPS').AsString;
      qryCekTps.Next;
    end;

    //cek jumlah pemilih dalam tps
    sql_hitungIsiTps := 'SELECT COUNT(ID_USER) AS JUML FROM pemilih_'+sDesa+' WHERE TPS = '+quotedStr(hasil)+' AND STATUS2 = ''0''';
    qryCekTps.Active := False;
    qryCekTps.SQL.Clear;
    qryCekTps.SQL.Text := sql_hitungIsiTps;
    qryCekTps.Active := True;
    qryCekTps.First;

    while not qryCekTps.Eof do begin
      jumlah_pemilih := qryCekTps.fieldByName('JUML').AsInteger;
      qryCekTps.Next;
    end;
    //jika jumlah pemilih dalam tps lebih dari 600, hasil = '0'
    if((jumlah_pemilih >= 600) and (copy(temp_tps,1,1) <> 'K')) then
      hasil := '0';
  end;
  result:= hasil;
end;

procedure TForm_TambahPemilih.Button2Click(Sender: TObject);
begin
  //untuk setiap baris
  //for i:=0 to cxGrid1TableView1.DataController.RecordCount-1 do begin

  //end;
end;

procedure TForm_TambahPemilih.btnCekClick(Sender: TObject);
begin
  //
  threadCek.ThreadDialog := threadDialogCek;
  threadCek.Execute(Self);
end;

procedure TForm_TambahPemilih.threadCekExecute(Sender: TObject;
  Params: Pointer);
var
  dobel, formatsalah : boolean;
  namalengkap, kelaminfull, kelamin, kawin : string;
  usia, i : integer;
begin
  dobel:=true;
  formatsalah:=true;
  gagal1:=tStringlist.Create;
  gagal2:=tStringlist.Create;
  gagal12:=tStringlist.Create;

  //cek di awal beud
  for i:=0 to cxGrid1TableView1.DataController.RecordCount-1 do begin
    namalengkap:= AnsiUpperCase(getVal(i,2));
    //usia := hitung(getTgl(i));
    usia := hitung(perbaikiTgl(getVal(i,4)));
    kelaminfull := AnsiUpperCase(StringReplace(getVal(i,5), ' ', '',[rfReplaceAll, rfIgnoreCase]));
    kelamin := AnsiUpperCase(Copy(StringReplace(getVal(i,5), ' ', '',[rfReplaceAll, rfIgnoreCase]),1,1));
    kawin :=  AnsiUpperCase(Copy(StringReplace(getVal(i,6), ' ', '',[rfReplaceAll, rfIgnoreCase]),1,1));
    if(namalengkap <> '') then
    begin
    if(((usia < 17) AND (kawin = 'B')) OR (usia = -1)) then begin
      //showmessage('gagal');
      formatsalah:=false;
    end;
    if((kawin<>'B') AND (kawin<>'S') AND (kawin<>'P')) then begin
      formatsalah:=false;
//        break;
    end;
    if(((kelamin<>'L') AND (kelamin<>'P')) OR (kelaminfull = 'PRIA')) then begin
      formatsalah:=false;
//        break;
    end;
    dobel:=cekForm2(i);
      //if not dobel2 then break;
      //showmessage(inttostr(usia));
    end;
    if((not formatsalah) and (not dobel)) then //dua2nya gagal
      gagal12.Add(inttostr(i))
    else if(dobel) then //salah format aja
      gagal1.Add(inttostr(i))
    else //dobel aja
      gagal2.Add(inttostr(i));
  end;
end;

procedure TForm_TambahPemilih.threadCekFinishAll(Sender: TObject);
var
  i, idx_wrn: integer;
begin
  //warnain yg gagal
  //gagal1
  for i:=0 to gagal1.Count-1 do begin
    idx_wrn := strtoint(gagal1[i]);
    //ngewarnain
    cxGrid1TableView1.DataController.SetValue(idx_wrn,15,'1');
  end;

  //gagal2
  for i:=0 to gagal2.Count-1 do begin
    idx_wrn := strtoint(gagal2[i]);
    //ngewarnain
    cxGrid1TableView1.DataController.SetValue(idx_wrn,15,'2');
  end;

  //gagal12
  for i:=0 to gagal12.Count-1 do begin
    idx_wrn := strtoint(gagal12[i]);
    //ngewarnain
    cxGrid1TableView1.DataController.SetValue(idx_wrn,15,'3');
  end;

  //free memory
  gagal1.Free;
  gagal2.Free;
  gagal12.Free;
end;

procedure TForm_TambahPemilih.cxGrid1TableView1CustomDrawCell(
  Sender: TcxCustomGridTableView; ACanvas: TcxCanvas;
  AViewInfo: TcxGridTableDataCellViewInfo; var ADone: Boolean);
begin
  {if AViewInfo.GridRecord.Values[15]<>'0' then
  begin
    ACanvas.Brush.Color:=clFuchsia;
    ACanvas.Font.Color:=clBlack;
  end;}
end;

end.

